/*
 * ValuesManager.java
 *
 * Created on 21. maj 2007, 15:26
 *
 * To change this template, choose Tools | Template Manager
 * and open the template in the editor.
 */

package sja.util.values;

import sja.util.Log;
import sja.util.Values;

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Properties;

/**
 * @author SEVI
 */
public class ValuesManager {

    private static final String SJA_ENVIRONMENT_SEPARATOR = ".";
    private static final String SJA_ENVIRONMENT_PREFIX = "sja" + SJA_ENVIRONMENT_SEPARATOR + "env";
    private static final String SJA_ENVIRONMENT_POSTFIX = "properties";
    // private static final String USER_DIR                = "user.dir";
    private static String ENV_FILENAME;
    private static final String SHARED_FILENAME = (SJA_ENVIRONMENT_PREFIX + SJA_ENVIRONMENT_SEPARATOR + "shared" + SJA_ENVIRONMENT_SEPARATOR + SJA_ENVIRONMENT_POSTFIX).toLowerCase();

    private static Properties envProperties;
    private static Properties sharedProperties;

    /**
     * Creates a new instance of ValuesManager
     */
    protected ValuesManager() {
    }

    static {
        load();
    }

    public static void load() {
        String sjaEnvironment = getEnvironment();
        ENV_FILENAME = (SJA_ENVIRONMENT_PREFIX + SJA_ENVIRONMENT_SEPARATOR + sjaEnvironment + SJA_ENVIRONMENT_SEPARATOR + SJA_ENVIRONMENT_POSTFIX).toLowerCase();
        envProperties = loadProperties(ENV_FILENAME);
        sharedProperties = loadProperties(SHARED_FILENAME);
    }

    private static String getEnvironment() {
        //get environmentname
        String sjaEnvironment = System.getProperty(SJA_ENVIRONMENT_PREFIX);
        //throw exception if it's not set
        if (sjaEnvironment == null || sjaEnvironment.equals("")) {
            String msg = "Environment is not set. You must add a parameter to the command line. Examples: 'java -D" + SJA_ENVIRONMENT_PREFIX + "=DEV', 'java -D" + SJA_ENVIRONMENT_PREFIX + "=prod' or whatever you call your environments";
            throwRuntime(msg);
        }
        return sjaEnvironment;
    }

    private static Properties loadProperties(String fileName) {
        Properties properties = new Properties();
        FileInputStream fis = null;
        try {
            fis = new FileInputStream(fileName);
        } catch (FileNotFoundException ex) {
            writeDefaultFile(fileName);
            String userDir = System.getProperty("user.dir");
            String msg = "File '" + fileName + "' was not found at '" + userDir + "'. A simple default file is being written at the location";
            throwRuntime(msg);
        }

        try {
            properties.load(fis);
        } catch (IOException ex) {
            ex.printStackTrace();
        }

        return properties;
    }

    public static String get(String prefkey) {
        String prop;
        prop = sharedProperties.getProperty(prefkey);

        if (prop == null || prop.equals("")) {
            prop = envProperties.getProperty(prefkey);
        }

        if (prop == null || prop.equals("")) {
            String msg = "The property '" + prefkey + "' was not set. Please edit the '" + SHARED_FILENAME + "' or the environment specific '" + ENV_FILENAME + "'";
            throwRuntime(msg);
        }
        return prop;
    }

    private static void throwRuntime(final String msg) {
        System.err.println(msg);
        Log.using(Values.class).error(msg);
        throw new RuntimeException(msg);
    }


    private static void writeDefaultFile(String fileName) {
        String comment = "This file was automatically created by the Values system in the correct location. Either expand this file with more values or copy your own file to this directory";
        Properties def = new Properties();
        def.setProperty("key", "value");
        def.setProperty("key2", "value2");
        FileOutputStream fos = null;

        try {
            fos = new FileOutputStream(fileName);
        } catch (FileNotFoundException ex) {
            ex.printStackTrace();
        }

        try {

            def.store(fos, comment);
            if (fos != null) {
                fos.close();
            }
        } catch (IOException ex) {
            ex.printStackTrace();
        }
    }
}
